from decimal import Decimal

from django.shortcuts import render
from django.views import View
from utils.views import LoginRequiredJsonMixin
# Create your views here.
from django_redis import get_redis_connection
from apps.goods.models import SKU
from apps.users.models import Address
from django.http import JsonResponse, HttpResponseBadRequest
import json
from apps.orders.models import OrderGoods, OrderInfo
import pickle, base64
from django.utils import timezone
from django.db import transaction
# 订单提交

class OrderCommitView(View):
    def post(self, request):
        '''订单提交'''
        # 拿到参数效验参数
        data_dict = json.loads(request.body.decode())
        address_id = data_dict.get('address_id')
        pay_method = data_dict.get('pay_method')

        if not all([address_id, pay_method]):
            return HttpResponseBadRequest('缺少参数')
        try:
            address = Address.objects.get(id=address_id)
        except Address.DoesNotExist:
            return HttpResponseBadRequest('没有地址')
        if pay_method not in [OrderInfo.PAY_METHODS_ENUM["ALIPAY"], OrderInfo.PAY_METHODS_ENUM["CASH"]]:
            return HttpResponseBadRequest('参数错误')

        user = request.user
        # 生成订单id
        order_id = timezone.localtime().strftime('%Y%m%d%H%M%S') + ('%09d' % user.id)

        with transaction.atomic():
            save_id = transaction.savepoint()

        # 保存数据到订单基础数据表
            order = OrderInfo.objects.create(
                order_id=order_id,
                user=user,
                address=address,
                total_count=0,
                total_amount=Decimal('0'),
                freight=Decimal('10.00'),
                pay_method=pay_method,
                status=OrderInfo.ORDER_STATUS_ENUM['UNPAID'] if pay_method == OrderInfo.PAY_METHODS_ENUM['ALIPAY'] else
                OrderInfo.ORDER_STATUS_ENUM['UNSEND']
            )


        # 拿到redis的数据
            redis_conn = get_redis_connection('carts')
            carts_sku_count = redis_conn.hgetall('carts_%s' % user.id)
            selected_list = redis_conn.smembers('selected_%s' % user.id)
            # 转int
            sku_dict = {}
            for sku_id in selected_list:
                sku_dict[int(sku_id)] = int(carts_sku_count[sku_id])


            # 判断库存
            # 拿到原始库存和销量
            for sku_id in sku_dict.keys():
                while True:
                    sku = SKU.objects.get(id=sku_id)
                    old_sku_stock = sku.stock  # 原始库存
                    old_sku_sales = sku.sales  # 原始销量
                    if sku.stock < sku_dict[sku.id]:
                        transaction.savepoint_rollback(save_id)
                        return HttpResponseBadRequest('库存不足')


                        # # 运算库存与销量
                        # sku.stock -= sku_dict[sku.id]
                        # sku.sales += sku_dict[sku.id]
                        # sku.save()


                    # 判断并保存数据
                    new_sku_stock = old_sku_stock - sku_dict[sku.id]
                    new_sku_sales = old_sku_sales + sku_dict[sku.id]

                    resuet = SKU.objects.filter(id=sku_id, stock=old_sku_stock).update(stock=new_sku_stock,
                                                                                        sales=new_sku_sales)
                    if resuet == 0:
                        continue

                # 保存数据到订单表
                    OrderGoods.objects.create(
                        order=order,
                        sku=sku,
                        count=sku_dict[sku.id],
                        price=sku.price,

                    )
                    break
        # 商品订单中总价和数量
        order.total_count += sku_dict[sku.id]
        order.total_amount += (sku_dict[sku.id] * sku.price)


        order.total_amount += order.freight
        order.save()
        transaction.savepoint_commit(save_id)
        pl = redis_conn.pipeline()
        pl.hdel('carts_%s' % user.id, *selected_list)
        pl.srem('selected_%s' % user.id, *selected_list)
        pl.execute()

        # 响应提交订单结果
        return JsonResponse({'code': 0, 'errmsg': '下单成功', 'order_id': order.order_id})






# 订单页面

class OrderSettlementView(LoginRequiredJsonMixin, View):
    def get(self, request):
        user = request.user
        # 从redis中拿到数据

        redis_conn = get_redis_connection('carts')
        carts_dict = redis_conn.hgetall('carts_%s' % user.id)
        selected_list = redis_conn.smembers('selected_%s' % user.id)
        skus = SKU.objects.filter(id__in=selected_list)

        cart = {}
        for sku_id in selected_list:
            cart[int(sku_id)] = int(carts_dict[sku_id])

        # 生成商品数据
        sku_list = []
        for sku in skus:
            sku_list.append({
                'id': sku.id,
                'name': sku.name,
                'default_image_url': sku.default_image.url,
                'count': cart[sku.id],
                'price': sku.price
            })


        # 拿到地址信息
        addresss = Address.objects.filter(user=user, is_deleted=False)


        # 生成地址数据
        addr_list = []
        for address in addresss:
            addr_list.append({
                'id': address.id,
                'province': address.province.name,
                'city': address.city.name,
                'district': address.district.name,
                'place': address.place,
                'receiver': address.receiver,
                'mobile': address.mobile
            })
            freight = Decimal('10.00')

            # 渲染界面
            context = {
                'addresses': addr_list,
                'skus': sku_list,
                'freight': freight,
            }

            return JsonResponse({'code': 0,
                                      'errmsg': 'ok',
                                      'context': context})